package com.smartwasser.yunhtgl.apphtgl.widget;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.util.AttributeSet;
import android.view.View;

import com.smartwasser.yunhtgl.apphtgl.R;

import java.util.ArrayList;
import java.util.List;

public class GestureDisplayView extends View {
    private static final String TAG = "GestureDisplayView";
    /**
     * 选中项
     */
    public List<Integer> mChooseList;

    private float mDotSize;

    private float mStartX;

    private float mStartY;

    private float mDrawX;

    private float mDrawY;

    private float mDotsSpace;

    private Paint mDotsPaint;

    private Paint mLinesPaint;

    private int mDefaultColor = Color.WHITE;

    private int mChooseColor = 0x50a8fd;

    private int mErrorColor = 0xf54a49;

    private int mCount = 3;

    private boolean mIsError = false;

    private boolean mInputEnd = false;

    public GestureDisplayView(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public GestureDisplayView(Context context, AttributeSet attrs,
                              int defStyle) {
        super(context, attrs);
        TypedArray a = context.getTheme().obtainStyledAttributes(attrs,
                R.styleable.GestureDisplayView, defStyle, 0);
        int n = a.getIndexCount();

        for (int i = 0; i < n; i++) {
            int attr = a.getIndex(i);
            switch (attr) {
                case R.styleable.GestureDisplayView_color_no_choose:
                    mDefaultColor = a.getColor(attr,
                            mDefaultColor);
                    break;
                case R.styleable.GestureDisplayView_color_choose:
                    mChooseColor = a.getColor(attr,
                            mChooseColor);
                    break;
                case R.styleable.GestureDisplayView_dots_count:
                    mCount = a.getInt(attr, 3);
                    break;
                case R.styleable.GestureDisplayView_color_error:
                    mErrorColor = a.getColor(attr, mErrorColor);
                default:
                    break;
            }
        }

        a.recycle();
        mChooseList = new ArrayList<Integer>();
        mDotsPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        mDotsPaint.setStyle(Paint.Style.FILL);
        mDotsPaint.setStrokeCap(Paint.Cap.ROUND);
        mDotsPaint.setStrokeJoin(Paint.Join.ROUND);
        mLinesPaint = new Paint(mDotsPaint);
        mLinesPaint.setStrokeWidth(3);
    }

    @Override
    protected void onLayout(boolean changed, int left, int top, int right,
                            int bottom) {
        super.onLayout(changed, left, top, right, bottom);
        float width = getWidth();
        float height = getHeight();
        float size;
        if (width > height) {
            size = height;
            mStartY = 0;
            mStartX = (width - height) / 2;
        } else {
            size = width;
            mStartY = (height - width) / 2;
            mStartX = 0;
        }
        //mCount * mDotSize + (mCount - 1) * mDotSize * 1.2 = size;
        mDotSize = size / (mCount + (mCount - 1) * 1.2f);
        mDotsSpace = mDotSize * 1.2f;
    }

    @Override
    protected void onDraw(Canvas canvas) {
        drawDots(canvas);
        drawConnectLine(canvas);
    }

    private void drawDots(Canvas canvas) {
        mDrawX = mStartX;
        mDrawY = mStartY;
        int size = mCount * mCount;
        for (int i = 0; i <= size; i++) {
            if (mChooseList.contains(i + 1)) {
                if (mIsError) {
                    mDotsPaint.setColor(mErrorColor);
                } else {
                    mDotsPaint.setColor(mChooseColor);
                }

            } else {
                mDotsPaint.setColor(mDefaultColor);
            }
            canvas.drawCircle(mDrawX + mDotSize / 2, mDrawY + mDotSize / 2, mDotSize / 2, mDotsPaint);
            if ((i + 1) % mCount == 0) {
                mDrawX = mStartX;
                mDrawY = mDrawY + mDotSize + mDotsSpace;
            } else {
                mDrawX = mDrawX + mDotSize + mDotsSpace;
            }
        }
    }

    /**
     * 绘制连接线
     *
     * @param canvas
     */
    private void drawConnectLine(Canvas canvas) {
        int size = mChooseList.size();
        if (size > 1) {
            float startX = -1;
            float startY = -1;
            if (mIsError) {
                mLinesPaint.setColor(mErrorColor);
            } else {
                mLinesPaint.setColor(mChooseColor);
            }
            for (int i = 0; i < mChooseList.size(); i++) {
                int id = mChooseList.get(i);
                int indexX = (id - 1) % mCount;
                int indexY = (id - 1) / mCount;
                float endX = indexX * (mDotSize + mDotsSpace) + mDotSize / 2 + mStartX;
                float endY = indexY * (mDotSize + mDotsSpace) + mDotSize / 2 + mStartY;
                if (startX != -1) {
                    canvas.drawLine(startX, startY, endX, endY, mLinesPaint);
                }
                startX = endX;
                startY = endY;
            }
        }
    }

    /**
     * 重置
     */
    public void reset() {
        mIsError = false;
        mChooseList.clear();
        postInvalidate();
    }

    /**
     * 新加选中ID
     *
     * @param id
     */
    public void addChoose(int id) {
        if (mInputEnd) {
            mIsError = false;
            mInputEnd = false;
            mChooseList.clear();
        }
        mChooseList.add(id);
        postInvalidate();
    }

    /**
     * 输入是否正确
     *
     * @param value true / false;
     */
    public void setError(boolean value) {
        mIsError = value;
        postInvalidate();
    }

    /**
     * 是否输入结束
     *
     * @param value
     */
    public void setInputOver(boolean value) {
        mInputEnd = value;
    }
}
